﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using XXF.BaseService.ServiceCenter.SystemRuntime;
using ZooKeeperNet;

namespace XXF.BaseService.ServiceCenter.ZK
{
    public class ZKNodeRegister : ZKBase
    {
        private CancellationTokenSource _cancelsource;
        private AutoResetEvent autoevent;
        private int _serviceid;
        private long _sessionid;
        private bool isdisposeing;

        public void Register(CancellationTokenSource cancelsource, int serviceid, long sessionid)
        {
            _serviceid = serviceid;
            _sessionid = sessionid;
            _cancelsource = cancelsource;
            autoevent = new AutoResetEvent(false);

            System.Threading.Tasks.Task.Factory.StartNew(() =>
            {
                CreateNodePathRun();
            }, _cancelsource.Token);

        }

        private void CreateNodePathRun()
        {
            while (!_cancelsource.IsCancellationRequested)
            {
                try
                {
                    var zk = GetZookeeper();
                    this.CreateRoot();
                    // 检查并创建服务根路径
                    string servicepath = this.GetServicePath(_serviceid);
                    var stat = zk.Exists(servicepath, false);
                    if (stat == null)
                    {
                        string strservicepath = zk.Create(servicepath, new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.Persistent);
                    }
                    //检查并创建节点路径
                    string nodepath = this.GetNodePath(_serviceid, _sessionid);
                    var stat2 = zk.Exists(nodepath, true);//监视节点
                    if (stat2 == null)
                    {
                        string strnodepath = zk.Create(nodepath, new byte[0], Ids.OPEN_ACL_UNSAFE, CreateMode.Ephemeral);
                        stat2 = zk.Exists(nodepath, true);//监视节点
                    }
                    autoevent.WaitOne();
                }
                catch (Exception exp)
                {
                    System.Threading.Thread.Sleep(SystemParamConfig.ZK_RegisterNode_FailConnect_ReConnect_Every_Time * 1000);
                    if (isdisposeing == false) { }
                }
            }
            Dispose();
        }

        public override void Process(WatchedEvent @event)
        {
            if (@event.State == KeeperState.Expired || @event.State == KeeperState.Disconnected)
            {
                if (autoevent != null)
                    autoevent.Set();
            }
        }

        public override void Dispose()
        {
            isdisposeing = true;
            try
            {
                if (_serviceid != 0)
                {
                    var zk = GetZookeeper();
                    //检查并创建节点路径
                    string nodepath = this.GetNodePath(_serviceid, _sessionid);
                    zk.Delete(nodepath, -1);
                }
            }
            catch
            {

            }

            if (autoevent != null)
            {
                autoevent.Set();
                autoevent.Dispose();
            }

            base.Dispose();
        }
    }
}
